<template>
  <div>
    <div style="background:#fff">
      <span class="upload" v-show="this.isupload=='1'||this.isupload=='2'"><slot/>
        <input class="change" id="id" type="file"
          @change="handleFileChange"
          ref="inputer"
        />
      </span>
      <ul id="content" v-show="this.imgpath!==''">
        <li @click="showPic"><img :src="this.imgpath" alt="" style="height:60px"></li>
      </ul>
      <div class="picContent" v-show="isshow" @click="hidepic">
        <img :src="this.imgpath" alt="" style="height:500px;position:relative">
      </div>
    </div>
    <div v-if="this.localfiletype=='02'" style="margin:30px 0">
      <p>{{localFilename}}</p>
    </div>
  </div>
</template>
<style>
</style>

<script>
import SparkMD5 from 'spark-md5';


const baseUrl = 'http://assets.eke88.com:5000';
let chunkSize = 1 * 1024 * 1024;

let file = null;
let fileSize = 0;
let chunks = 5;
let blobSlice;
let currentChunk = 0;
let fileReader;


export default {

  watch: {
    imagefile() {
      if (this.imagefile) {
        this.imgpath = this.imagefile[this.tn];
      } else {
        this.imgpath = '';
      }
    },
  },
  props: {
    tn: {
      type: String,
    },
    imagefile: {
      type: Object,
    },
    localfiletype: {
      type: String,
    },
    isupload: {
      type: String,
    },
  },

  data() {
    return {
      shouPic: true,
      debug: false,
      ts: this.newStore(),
      aa: this.newStore(),
      list: [],
      imgpath: '',
      isshow: false,
      localFilename: '',
    };
  },
  methods: {

    changePic(pic) {
      this.imgpath = pic;
      this.imagefile[this.tn] = pic;
      // alert(this.tn);
      // this.$emit('getTestinput', this.imgpath, this.tn);
    },
    showPic() {
      this.isshow = true;
    },
    hidepic() {
      this.isshow = false;
    },
    handleFileChange() {
      const inputDOM = this.$refs.inputer;
      const [tfile] = inputDOM.files;
      file = tfile;
      this.errText = '';
      if (!file) {
        return;
      }
      fileSize = Math.floor(file.size);

      // alert(fileSize);
      // 提示
      this.localFilename = file.name;
      this.responseChange(file);
    },
    async upload(i, fileMd5Value, pchunks) {
      return new Promise((resolve) => {
      // 构造一个表单，FormData是HTML5新增的
        const end = (i + 1) * chunkSize >= file.size ? file.size : (i + 1) * chunkSize;
        const form = new FormData();
        form.append('data', file.slice(i * chunkSize, end)); // file对象的slice方法用于切出文件的一部分
        form.append('total', pchunks); // 总片数
        form.append('index', i); // 当前是第几片
        form.append('fileMd5Value', fileMd5Value);
        this.spost(this.ts, `${baseUrl}/upload`, form).then((ts) => {
          resolve(ts.d.desc);
        }).catch((ts) => { resolve(ts.d.desc); });
      });
    },
    async checkAndUploadChunk(fileMd5Value, chunkList) {
      return new Promise((resolve) => {
        chunks = Math.ceil(fileSize / chunkSize);
        const promiselist = [];

        for (let i = 0; i < chunks; i += 1) {
          const exit = chunkList.indexOf(`${i}`) > -1;
          // 如果已经存在, 则不用再上传当前块
          if (!exit) {
            promiselist.push(this.upload(i, fileMd5Value, chunks));
          }
        }
        Promise.all(promiselist).then(() => { resolve(); });
      });
    },

    async  checkFileMD5(fileName, fileMd5Value) {
      return new Promise((resolve) => {
        const url = `${baseUrl}/check/file`;
        this.sget(this.ts, url, { fileName, fileMd5Value }).then((ts) => {
          resolve(ts.d);
        });
      }).catch((reject) => { reject(); });
    },


    notifyServer(fileMd5Value) {
      // alert(111111111111111111);
      const url = `${baseUrl}/merge?md5=${fileMd5Value}&fileName=${file.name}&size=${file.size}`;
      this.sget(this.ts, url, {}).then((ts) => {
        const pic = `${baseUrl}/nodeServer/uploads/${ts.d.fname}`;
        this.changePic(pic);
      });
    },

    loadNext() {
      const start = currentChunk * chunkSize;
      const end = ((start + chunkSize) >= file.size) ? file.size : start + chunkSize;

      fileReader.readAsArrayBuffer(blobSlice.call(file, start, end));
    },
    async  md5File(pfile) {
      return new Promise((resolve) => {
        blobSlice = File.prototype.slice || File.prototype.mozSlice || File.prototype.webkitSlice;

        chunkSize = pfile.size / chunks;

        currentChunk = 0;
        const spark = new SparkMD5.ArrayBuffer();
        fileReader = new FileReader();

        fileReader.onload = (e) => {
          spark.append(e.target.result);

          currentChunk += 1;

          if (currentChunk < chunks) {
            this.loadNext();
          } else {
            // const cur = +(new Date());
            // console.log('finished loading');
            // alert(spark.end() + '---' + (cur - pre)); // Compute hash
            const result = spark.end();
            resolve(result);
          }
        };

        fileReader.onerror = () => {
          console.warn('oops, something went wrong.');
        };


        this.loadNext();
      }).catch((reject) => { reject(); });
    },

    async  responseChange(pfile) {
      // 第一步：按照 修改时间+文件名称+最后修改时间-->MD5
      // 显示文件校验进度

      const fileMd5Value = await this.md5File(pfile);

      const fileName = fileMd5Value.concat('.', pfile.name.split('.')[pfile.name.split('.').length - 1]);
      // 第二步：校验文件的MD5
      const result = await this.checkFileMD5(fileName, fileMd5Value);

      // 如果文件已存在, 就秒传
      if (result.file) {
        const pic = `${baseUrl}/nodeServer/uploads/${fileName}`;
        // console.log(this.imgpath);
        this.changePic(pic);
        return;
      }
      // let exit = false
      // 显示文件上传进度


      this.checkAndUploadChunk(fileMd5Value, result.chunkList).then(() => {
        this.notifyServer(fileMd5Value);
      });


      // 第四步: 通知服务器所有分片已上传完成


      // console.log(this.notifyServer);
    },
    verificationPicFile(pfile) {
      const fileTypes = ['.jpg', '.png'];
      const filePath = pfile.value;
      // 当括号里面的值为0、空字符、false 、null 、undefined的时候就相当于false
      if (filePath) {
        let isNext = false;
        const fileEnd = filePath.substring(filePath.indexOf('.'));
        for (let i = 0; i < fileTypes.length; i += 1) {
          if (fileTypes[i] === fileEnd) {
            isNext = true;
            break;
          }
        }
        if (!isNext) {
          alert('不接受此文件类型');
          pfile.value = '';
          return false;
        }
      } else {
        return false;
      }
      return true;
    },
  },
};

</script>
<style scoped lang="stylus" rel="stylesheet/stylus">
 .info-wrapper .info-content .upload-btn[data-v-0cbaa4e1]
  background #fff
 .picContent
    position: fixed;
    top 150px;
    right: 0;
    left: 0;
    margin: 0;
    margin: 0 auto;
    z-index: 5000;
    width 56%
 .upload
    padding: 7px 3px
    height: 33px
    line-height: 33px
    position: relative
    background: #69f
    border-radius: 3px
    text-decoration: none
    color: #fff
    .change
        position: absolute
        overflow: hidden
        right: 0
        top: 0
        opacity: 0
        width 86px
        height 33px
  ul
    margin-top: 2px
    font-size: 14px
</style>
